package com.ysw.http系列.rest_template;

import cn.hutool.core.map.MapUtil;
import com.google.common.collect.Maps;
import com.ysw.bean.User;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;

import java.util.HashMap;
import java.util.Map;

/**
 * @author: yu_sw
 * @Description: com.ysw.http系列.rest_template
 * @date:2022/5/20 22:09
 */
@Service
@Slf4j
public class RestTemplateService {
    @Autowired
    private RestTemplate restTemplate;

    public static final String HTTP_URL = "http://localhost:8088/%s";

    /**
     * url 参数提交 http://xxxx/xxx?xxx={key1}&xxx={key2}
     * 通常使用两种方式传递参数，够用了
     * 1. map 方式  注意map key的类型
     * 2. 使用路径变量顺序进行传递
     *
     * @return
     */
    public User testForObject() {
        String url = String.format(HTTP_URL, "getForObject");
        String appendUrl = new StringBuilder(url).append("?name={name}&id={id}").toString();
        //Map<Object, Object> params = MapUtil.builder().put("name", "张三").put("id", 1).build();//key如果是Object类型他是无法获取占位值的
        //使用map传递参数 注意 注意 注意，这里一定要是 String Object
        HashMap<String, Object> params = Maps.newHashMap();
        params.put("name", "zzz");
        params.put("id", 2);
        User forObject = restTemplate.getForObject(appendUrl, User.class, params);
        //根据路径变量传递参数
        User forObject1 = restTemplate.getForObject(appendUrl, User.class, "张三", 3);
        return forObject1;
    }


    /**
     * test case2 一般不使用这种骚方式
     * 使用multipart/form-data表单提交
     *
     * @return
     */
    public User testForObjectWithFormData() {
        String url = String.format(HTTP_URL, "getForObject");
        Map<Object, Object> params = MapUtil.builder().put("name", "张三").put("id", 1).build();
        HttpHeaders httpHeaders = new HttpHeaders();
        httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
        //httpHeaders.set("Content-Type", "multipart/form-data");
        HttpEntity<Map<Object, Object>> mapHttpEntity = new HttpEntity<>(params, httpHeaders);
        User result = restTemplate.getForObject(url, User.class, mapHttpEntity);
        log.info("get for object result:{}", result);
        return result;
    }

    /**
     * 对应的getForObject 其实就是对Object多了一个响应具体信息
     *
     * @return
     */
    public ResponseEntity testForEntity() {
        String url = String.format(HTTP_URL, "getForObject");
        String appendUrl = new StringBuilder(url).append("?name={name}&id={id}").toString();
        //Map<Object, Object> params = MapUtil.builder().put("name", "张三").put("id", 1).build();//key如果是Object类型他是无法获取占位值的
        //使用map传递参数 注意 注意 注意，这里一定要是 String Object
        HashMap<String, Object> params = Maps.newHashMap();
        params.put("name", "zzz");
        params.put("id", 2);
        ResponseEntity<User> getForEntity1 = restTemplate.getForEntity(appendUrl, User.class, params);
        //根据路径变量传递参数
        ResponseEntity<User> getForEntity = restTemplate.getForEntity(appendUrl, User.class, "张三", 3);
        User body = getForEntity.getBody();
        System.out.println(getForEntity.getStatusCode());
        return getForEntity;
    }

    /**
     * test for postForObject
     * 使用表单提交，这里要注意，使用表单提交的话一定要使用  MultiValueMap 来进行参数传递，不然会报错
     */
    public User testPostForObject_formData() {
        String url = String.format(HTTP_URL, "testForPost");
        HttpHeaders httpHeaders = new HttpHeaders();
        httpHeaders.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
        LinkedMultiValueMap<String, Object> params = new LinkedMultiValueMap<>();
        params.add("name", "张三");
        params.add("id", 2);
        HttpEntity httpEntity = new HttpEntity<>(params, httpHeaders);
        User user = restTemplate.postForObject(url, httpEntity, User.class);
        System.out.println(user);
        return user;
    }

    /**
     * 类似get路径传递参数
     */
    public User testPostForObject_url() {
        String url = String.format(HTTP_URL, "testForPost");
        String appendUrl = new StringBuilder(url).append("?name={name}&id={id}").toString();
        HashMap<String, Object> params = Maps.newHashMap();
        params.put("name", "张三");
        params.put("id", 2);
        User user = restTemplate.postForObject(appendUrl, null, User.class, params);
        System.out.println(user);
        return user;
    }

    /**
     * 类似get路径传递参数 post传参
     * 默认是采用 application/json
     */
    public User testPostForObject_requestBody() {
        String url = String.format(HTTP_URL, "testForPost");
        HashMap<String, Object> params = Maps.newHashMap();
        params.put("name", "张三");
        params.put("id", 2);
        User user = restTemplate.postForObject(url, params, User.class);
        System.out.println(user);
        return user;
    }
}
